<?php
// +----------------------------------------------------------------------
// | Bwsaas
// +----------------------------------------------------------------------
// | Copyright (c) 2015~2020 http://www.buwangyun.com All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Gitee ( https://gitee.com/buwangyun/bwsaas )
// +----------------------------------------------------------------------
// | Author: buwangyun <hnlg666@163.com>
// +----------------------------------------------------------------------
// | Date: 2020-9-28 10:55:00
// +----------------------------------------------------------------------

namespace app\manage\controller\member;

use buwang\base\MemberBaseController;
use buwang\facade\WechatMp;
use buwang\traits\CrudControllerTrait;
use think\facade\View;

class WechatKeyword extends MemberBaseController
{
    use \buwang\traits\Crud;

    protected $model = null;//模型实例
    protected $relationSearch = true;

    /**
     * 消息类型
     * @var array
     */
    public $types = [
        'text' => '文字', 'news' => '图文', 'image' => '图片', 'music' => '音乐',
        'video' => '视频', 'voice' => '语音', 'customservice' => '转客服',
    ];

    protected function initialize()
    {
        parent::initialize();
        $this->layout && $this->app->view->engine()->layout($this->layout);
        $this->model = new \app\common\model\WechatKeys();
    }

    public function index()
    {
        $miniapp = WechatMp::getWechatObj($this->member_miniapp_id);
        if (!$miniapp) return $this->error_jump('未正确配置接入公众号', NOT_JUMP);
        if ($this->request->isAjax()) {
            if (input('selectFieds')) {
                return $this->selectList();
            }
            list($page, $limit, $where) = $this->buildTableParames();
            $where[] = ['keys', '<>', 'subscribe'];
            $count = $this->model
                ->withJoin('memberMiniapp', 'LEFT')
                ->where('memberMiniapp.member_id', $this->user->top_id)
                ->where($where)
                ->count();
            $list = $this->model
                ->withJoin('memberMiniapp', 'LEFT')
                ->where('memberMiniapp.member_id', $this->user->top_id)
                ->where($where)
                ->page($page, $limit)
                ->order($this->sort)
                ->select();
            $data = [
                'total' => $count,
                'list' => $list,
            ];
            return $this->success('success', $data);
        }
        return view();
    }

    /**
     * 编辑
     * @menu true
     * @param int $id
     */
    public function edit($id = 0)
    {
        $row = $this->model->find($id);

        if (request()->isPost()) {
            if (!$row) return $this->error('记录不存在');

            $param = request()->post();
            //TODO 参数验证

            $this->model->startTrans();
            try {
                //TODO 更新记录
                $row->save($param);
                $this->model->commit();
            } catch (\Exception $e) {
                $this->model->rollback();
                return $this->error('编辑失败', ['errorMsg' => $e->getMessage()]);
            }
            return $this->success('编辑成功');
        }

        if (!$row) return $this->error('记录不存在');

        View::assign('row', $row);
        return view();
    }

    /**
     * 添加回复规则
     * @param string $keysDefault
     * @return \think\Response|\think\response\View
     */
    public function addKeys($keysDefault = '')
    {
        $data = $this->request->param();
        if ($keysDefault) $data['keys'] = $keysDefault;
        $this->isMemberAppAuth();

        if ($this->request->isGet()) {
            $msgTypes = $this->types;
            $root = rtrim(dirname($this->request->basefile(true)), '\\/');
            $defaultImage = "{$root}/static/manage/images/image.png";
            $subscribeData = null;
            if (in_array($keysDefault, ['subscribe', 'default'])) {
                if (!$this->member_miniapp) return $this->error_jump("应用信息不存在！");
                if (!$this->member_miniapp->mp_appid) return $this->error_jump("未正确配置公众号appid！");
                $subscribeData = $this->app->db->name('WechatKeys')->where('keys', '=', 'subscribe')->where('member_miniapp_id', '=', $this->member_miniapp_id)->find();
            }
            return view('add_keys', ['msgTypes' => $msgTypes, 'defaultImage' => $defaultImage, 'keysDefault' => $keysDefault, 'subscribeData' => $subscribeData]);
        }
        if ($this->request->isPost()) {
            //获取公众号或者小程序的APPID
            $appid = $keysDefault === 'subscribe' ? $this->member_miniapp->mp_appid : (isset($data['miniapp_type']) ? $this->member_miniapp->mp_appid : $this->member_miniapp->miniapp_appid);
            if (!$data['keys']) return $this->error("请输入关键词！");
            $db = $this->app->db->name('WechatKeys')->where('keys', $data['keys'])->where('member_miniapp_id', '=', $this->member_miniapp_id)->where('appid', '=', $appid);
            empty($data['id']) || $db->where('id', '<>', $data['id']);
            if ($db->count() > 0 && !in_array($keysDefault, ['subscribe', 'default'])) {
                return $this->error('关键字已经存在，请使用其它关键字！');
            }
            $update = [];
            switch ($data['type']) {
                case 'news':
                    $update['news_id'] = $data['news_id'];
                    break;
                case 'text':
                case 'customservice':
                    $update['content'] = $data['content'];
                    break;
                case 'image':
                    $update['image_url'] = $data['image_url'];
                    break;
                case 'video':
                    $update['video_title'] = $data['video_title'];
                    $update['video_desc'] = $data['video_desc'];
                    $update['video_url'] = $data['video_url'];
                    break;
                case 'music':
                    $update['music_title'] = $data['music_title'];
                    $update['music_url'] = $data['music_url'];
                    $update['music_desc'] = $data['music_desc'];
                    $update['music_image'] = $data['music_image'];
                    break;
                case 'voice':
                    $update['voice_url'] = $data['voice_url'];
                    break;
            }
            $update['create_by'] = $this->uid;
            $update['keys'] = $data['keys'];
            $update['status'] = $data['status'];
            $update['type'] = $data['type'];
            $update['appid'] = $appid ?: '';
            $update['member_miniapp_id'] = $this->member_miniapp_id;
            if (in_array($keysDefault, ['subscribe', 'default'])) {
                $find = $db->find();
                $result = $find ? $this->app->db->name('WechatKeys')->where('id', '=', $find['id'])->strict(true)->update($update) : $this->app->db->name('WechatKeys')->strict(true)->insert($update);
            }
            !in_array($keysDefault, ['subscribe', 'default']) && $result = $this->app->db->name('WechatKeys')->strict(true)->insert($update);
            if ($result !== false) {
                return $this->success('添加恭喜, 关键字保存成功！');
            } else {
                return $this->error('关键字保存失败, 请稍候再试！');
            }
        }
    }

    /**
     * 配置关注回复
     */
    public function subscribe()
    {
        return $this->addKeys('subscribe');
    }

    /**
     * 添加图文
     */
    public function addMaterial()
    {
        $id = $this->request->param('id/d', 0);
        if ($this->request->isGet()) {
            if ($this->request->param('output') === 'json') return $this->success('获取成功', ($id > 0 ? $this->news($id) : []));
            return view('form');
        } else {
            $data = $this->request->post('data', []);
            $update = [
                'create_by' => $this->uid,
                'article_id' => $this->_buildArticle($data),
                'member_miniapp_id' => $this->member_miniapp_id,
            ];
            if ($id > 0 && ($this->app->db->name('WechatNews')->where(['id' => $id])->find() !== false)) {
                $update['id'] = $id;
                if ($this->app->db->name('WechatNews')->update($update) !== false) {
                    return $this->success('图文更新成功！');
                } else {
                    return $this->error('图文更新失败，请稍候再试！');
                }
            } else {
                if ($this->app->db->name('WechatNews')->insert($update) !== false) {
                    return $this->success('图文添加成功！');
                } else {
                    return $this->error('图文添加失败，请稍候再试！');
                }
            }

        }
    }

    /**
     * 删除微信图文
     */
    public function removeMaterial()
    {
        $this->model = new \app\common\model\WechatNews();
        if (request()->isPost()) {
            $id = $this->request->param('id/d');
            if (!$id) return $this->error('参数有误');
            $this->isMemberAppAuth();
            $pk = $this->model->getPk();
            $list = $this->model->where($pk, $id)->where(['member_miniapp_id' => $this->member_miniapp_id])->find();
            if (!$list) return $this->error('记录不存在');
            $this->model->startTrans();
            try {
                $maps = ['id' => $id, 'member_miniapp_id' => $this->member_miniapp_id];
                $list->update(['is_deleted' => '1'], $maps);
                $this->model->commit();
            } catch (\Exception $e) {
                $this->model->rollback();
                return $this->error('删除失败:' . $e->getMessage());
            }
            return $this->success('删除成功');
        }
    }

    /**
     * 图文选择器
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    public function select()
    {
        return $this->materialList('select');
    }

    /**
     * 图文列表
     */
    public function materialList($tempate = 'material_list')
    {
        $limit = $this->request->param('limit/d', 10);
        $page = $this->request->param('page/d', 1);
        $this->isMemberAppAuth();//保证有租户应用信息
        $miniapp = WechatMp::getWechatObj($this->member_miniapp_id);
        if (!$miniapp) return $this->error_jump('未正确配置接入公众号', NOT_JUMP);
        if ($page) {
            if ($limit > 0) {
                $limit = intval($limit);
            } else {
                $limit = $this->app->request->get('limit', $this->app->cookie->get('limit'));
                $this->app->cookie->set('limit', $limit = intval($limit >= 10 ? $limit : 20));
            }
            [$options, $query] = ['', $this->request->get()];
            $pager = $this->app->db->name('WechatNews')->where(['is_deleted' => '0'])->where(['member_miniapp_id' => $this->member_miniapp_id])->order('id desc')->paginate(['list_rows' => $limit, 'query' => $query], false);
            foreach ([10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 110, 120, 130, 140, 150, 160, 170, 180, 190, 200] as $num) {
                [$query['limit'], $query['page'], $selects] = [$num, 1, $limit === $num ? 'selected' : ''];
                if (stripos($this->request->get('spm', '-'), 'm-') === 0) {
                    $url = url('@admin') . '#' . $this->app->request->baseUrl() . '?' . urldecode(http_build_query($query));
                } else {
                    $url = $this->app->request->baseUrl() . '?' . urldecode(http_build_query($query));
                }
                $options .= "<option data-num='{$num}' value='{$url}' {$selects}>{$num}</option>";
            }
            $selects = "<select onchange='location.href=this.options[this.selectedIndex].value' data-auto-none>{$options}</select>";
            $pagetext = lang('bw_page_html', [$pager->total(), $selects, $pager->lastPage(), $pager->currentPage()]);
            $pagehtml = "<div class='pagination-container nowrap'><span>{$pagetext}</span>{$pager->render()}</div>";
            if (stripos($this->app->request->get('spm', '-'), 'm-') === 0) {
                view::assign('pagehtml', preg_replace('|href="(.*?)"|', 'data-open="$1" onclick="return false" href="$1"', $pagehtml));
            } else {
                view::assign('pagehtml', $pagehtml);
            }
            $result = ['page' => ['limit' => intval($limit), 'total' => intval($pager->total()), 'pages' => intval($pager->lastPage()), 'current' => intval($pager->currentPage())], 'list' => $pager->items()];
        } else {
            $list = $this->app->db->name('WechatNews')->where(['is_deleted' => '0'])->where(['member_miniapp_id' => $this->member_miniapp_id])->order('id desc')->select()->toArray();

            $result = ['list' => $list];
        }
        $this->data_filter($result['list']);
        if (!in_array($tempate, ['material_list', 'select'])) return $this->error_jump("参数错误");
        return view($tempate, $result);
    }

    /**
     * 图文列表数据处理
     * @param array $data
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    protected function data_filter(&$data)
    {
        foreach ($data as &$vo) {
            $vo = $this->news($vo['id']);
        }
    }

    /**
     * 通过图文ID读取图文信息
     * @param integer $id 本地图文ID
     * @param array $where 额外的查询条件
     * @return array
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    protected function news($id, $where = [])
    {
        $data = $this->app->db->name('WechatNews')->where(['id' => $id])->where($where)->find();
        list($data['articles'], $articleIds) = [[], explode(',', $data['article_id'])];
        $articles = $this->app->db->name('WechatNewsArticle')->whereIn('id', $articleIds)->select();
        foreach ($articleIds as $article_id) foreach ($articles as $article) {
            if (intval($article['id']) === intval($article_id)) array_push($data['articles'], $article);
            unset($article['create_by'], $article['create_at']);
        }
        return $data;
    }

    /**
     * 图文更新操作
     * @param array $data
     * @param array $ids
     * @return string
     * @throws \think\db\exception\DbException
     */
    private function _buildArticle($data, $ids = [])
    {
        foreach ($data as $vo) {
            if (empty($vo['digest'])) {
                $vo['digest'] = mb_substr(strip_tags(str_replace(["\s", '　'], '', $vo['content'])), 0, 120);
            }
            $vo['create_at'] = date('Y-m-d H:i:s');
            if (empty($vo['id'])) {
                $result = $id = $this->app->db->name('WechatNewsArticle')->insertGetId($vo);
            } else {
                $id = intval($vo['id']);
                $result = $this->app->db->name('WechatNewsArticle')->where('id', $id)->update($vo);
            }
            if ($result !== false) array_push($ids, $id);
        }
        return join(',', $ids);
    }

    /**
     * 图文展示
     * @param integer $id 图文ID
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    public function previewNews($id = 0)
    {
        $id = empty($id) ? input('id') : $id;
        $news = [];
        if ($id > 0) $news = $this->news($id);
        return $this->fetch('member/wechat_keyword/preview/news', compact("news", "id"));
    }

    /**
     * 文章展示
     * @param integer $id 文章ID
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    public function previewView($id = 0)
    {
        $where = ['id' => empty($id) ? input('id') : $id];
        $this->app->db->name('WechatNewsArticle')->where($where)->update([
            'read_num' => $this->app->db->raw('read_num+1')
        ]);
        $this->info = $this->app->db->name('WechatNewsArticle')->where($where)->find();
        View::assign('info', $this->info);
        if ($this->info['content_source_url']) return $this->redirect($this->info['content_source_url']);
        return $this->fetch();
    }

    /**
     * 文本展示
     */
    public function previewText()
    {
        $content = strip_tags(input('content', ''), '<a><img>');
        return $this->fetch('member/wechat_keyword/preview/text', compact("content"));
    }

    /**
     * 图片展示
     */
    public function previewImage()
    {
        $content = strip_tags(input('content', ''), '<a><img>');
        return $this->fetch('member/wechat_keyword/preview/image', compact("content"));
    }

    /**
     * 视频展示
     */
    public function previewVideo()
    {
        $url = strip_tags(input('url', ''), '<a><img>');
        $title = strip_tags(input('title', ''), '<a><img>');
        return $this->fetch('member/wechat_keyword/preview/video', compact("url", "title"));
    }

    /**
     * 语音展示
     */
    public function previewVoice()
    {
        $url = strip_tags(input('url', ''), '<a><img>');
        return $this->fetch('member/wechat_keyword/preview/voice', compact("url"));
    }

    /**
     * 音乐展示
     */
    public function previewMusic()
    {
        $url = strip_tags(input('url', ''), '<a><img>');
        $desc = strip_tags(input('desc', ''), '<a><img>');
        $title = strip_tags(input('title', ''), '<a><img>');
        return $this->fetch('member/wechat_keyword/preview/music', compact("url", "desc", "title"));
    }
}
